package com.mjk.common.tools.gson.adapter;

import com.google.gson.FieldNamingStrategy;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.TypeAdapter;
import com.google.gson.reflect.TypeToken;
import com.mjk.common.tools.gson.adapter.impl.*;

import javax.sql.rowset.serial.SerialClob;
import java.lang.reflect.Field;
import java.math.BigDecimal;
import java.sql.Blob;
import java.sql.Clob;
import java.sql.Time;
import java.sql.Timestamp;
import java.time.Instant;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.util.Date;
import java.util.Map;

/**
 * GSON 类型转化
 * @author mjk
 *
 */
public enum BeeGsonAdapterType {
	//STRING(String.class,new StringAdapterImpl()),
	CLOB(Clob.class,new ClobAdapterImpl()),
	BLOB(Blob.class, new BlobAdapter()),
	BIGDECIMAL(BigDecimal.class,new BigDecimalAdapterImpl()),
	TIMESTAMP(Timestamp.class,new TimestampAdapterImpl()),
	TIME(Time.class,new TimeAdapterImpl()),
	DATE(Date.class,new DateAdapterImpl()),
	SERIALCLOB(SerialClob.class,new ClobAdapterImpl()),
	INSTANT(Instant.class,new InstantTypeAdapterImpl()),
	LOCALDATETIME(LocalDateTime.class, new LocalDateTimeAdapterImpl()),
	LOCALTIME(LocalTime.class, new LocalTimeAdapterImpl()),
	LOCALDATE(LocalDate.class, new LocalDateAdapterImpl()),
	MAP(Map.class,new MapAdapterImpl())
	//BEERESPONSE(BeeResponse.class,new BeeResponseTypeAdapter());
	;
	
	private final Class<?> clazz;
	
	@SuppressWarnings({"rawtypes" })
	private final TypeAdapter adapter;
	
	@SuppressWarnings("rawtypes")
    BeeGsonAdapterType(Class<?> clazz, TypeAdapter adapter){
		this.clazz = clazz;
		this.adapter = adapter;
	}
	
	public static Gson getGson(boolean isNull){
		GsonBuilder build = new GsonBuilder();
		build.setPrettyPrinting().disableHtmlEscaping().setDateFormat("yyyy-MM-dd HH:mm:ss");
		if(isNull){
			build.serializeNulls();
			build.registerTypeAdapter(String.class, new StringAdapterImpl());
		}
		for (BeeGsonAdapterType type : BeeGsonAdapterType.values()) {
			if(type.clazz.equals(Map.class)){
				build.registerTypeAdapter(new TypeToken<Map>(){}.getType(), type.adapter);
			}else{
				build.registerTypeAdapter(type.clazz, type.adapter);
			}
		}
        return build.create();
	}

	static class CustemFieldNamingStrategy implements FieldNamingStrategy{
		@Override
		public String translateName(Field field) {
			String fieldName = field.getName();
			return fieldName.toLowerCase();
		}
	}
}
